using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Web.UI;
using System.Web.UI.WebControls;

namespace Xacc
{
	partial class PropertyGrid
	{
		#region Fields

		Style
			m_itemValueStyle,
			m_itemNameStyle,
			m_selectedItemValueStyle,
			m_selectedItemNameStyle,
			m_headerStyle,
			m_footerStyle;

		#endregion Fields

		#region Properties

		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Property value style")]
		public Style ItemValueStyle {
			get {
				return this.m_itemValueStyle ?? (this.m_itemValueStyle = this.InitNewStyle());
			}
		}
		
		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Property name style")]
		public Style ItemNameStyle {
			get {
				return this.m_itemNameStyle ?? (this.m_itemNameStyle = this.InitNewStyle());
			}
		}

		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Selected property value style")]
		public Style SelectedItemValueStyle {
			get {
				return this.m_selectedItemValueStyle ?? (this.m_selectedItemValueStyle = this.InitNewStyle());
			}
		}

		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Selected property name style")]
		public Style SelectedItemNameStyle {
			get {
				return this.m_selectedItemNameStyle ?? (this.m_selectedItemNameStyle = this.InitNewStyle());
			}
		}

		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Header style")]
		public Style HeaderStyle {
			get {
				return this.m_headerStyle ?? (this.m_headerStyle = this.InitNewStyle());
			}
		}

		[Category("Styles"),
			DefaultValue((string)null),
			DesignerSerializationVisibility(DesignerSerializationVisibility.Content),
			NotifyParentProperty(true),
			PersistenceMode(PersistenceMode.InnerProperty),
			Description("Footer style")]
		public Style FooterStyle {
			get {
				return this.m_footerStyle ?? (this.m_footerStyle = this.InitNewStyle());
			}
		}

		#endregion Properties

		#region Methods

		Style InitNewStyle()
		{
			Style _result = new Style();
			if (this.IsTrackingViewState) {
				((IStateManager)_result).TrackViewState();
			}
			return _result;
		}

		IEnumerable<Style> EnumerateStyles()
		{
			return new[] {
				this.m_itemValueStyle,
				this.m_itemNameStyle,
				this.m_selectedItemValueStyle,
				this.m_selectedItemNameStyle,
				this.m_headerStyle,
				this.m_footerStyle,
			};
		}

		protected override void TrackViewState()
		{
			base.TrackViewState();

			Array.ForEach(this.EnumerateStyles().ToArray(), _s => {
				if (null != _s) {
					((IStateManager)_s).TrackViewState();
				}
			});
		}

		protected override object SaveViewState()
		{
			var _styles =
				from _style in this.EnumerateStyles()
				select _style != null
					? ((IStateManager)_style).SaveViewState()
					: null;
			
			var objArray = new[] { base.SaveViewState() }.Concat(_styles);
				
			return
				objArray.SkipWhile(o => null == o).Any()
					? objArray.ToArray()
					: null;
		}

		protected override void LoadViewState(object savedState)
		{
			if (null != savedState) {
				object[] _state = (object[])savedState;
				
				base.LoadViewState(_state[0]);
				
				var _index = 1;
				
				this.EnumerateStyles().Cast<IStateManager>().ToList().ForEach(_style => {
					if (null != _state[_index++]) {
						_style.LoadViewState(_state[_index]);
					}
				});
			} else {
				base.LoadViewState(savedState);
			}
		}

		#endregion Methods
	}
}
